//
//  NSDate+Utilities.m
//  MengLiao
//
//  Created by xiuxin on 2022/7/15.
//  Copyright © 2022 BaseBusiness. All rights reserved.
//

#import "NSDate+Utilities.h"
#define D_WEEK        604800
#define D_HOUR        3600
static const unsigned componentFlags = (NSCalendarUnitYear| NSCalendarUnitMonth | NSCalendarUnitDay | NSCalendarUnitWeekOfYear |  NSCalendarUnitHour | NSCalendarUnitMinute | NSCalendarUnitSecond | NSCalendarUnitWeekday | NSCalendarUnitWeekdayOrdinal);

@implementation NSDate (Utilities)

- (NSUInteger)day {
    return [NSDate day:self];
}

- (NSUInteger)month {
    return [NSDate month:self];
}

- (NSUInteger)year {
    return [NSDate year:self];
}

- (NSUInteger)hour {
    return [NSDate hour:self];
}

- (NSUInteger)minute {
    return [NSDate minute:self];
}

- (NSUInteger)second {
    return [NSDate second:self];
}

+ (NSUInteger)day:(NSDate *)date {
    NSCalendar *calendar = [NSCalendar currentCalendar];
    
#if __IPHONE_OS_VERSION_MIN_REQUIRED >= __IPHONE_8_0
    // NSDayCalendarUnit
    NSDateComponents *dayComponents = [calendar components:(NSCalendarUnitDay) fromDate:date];
#else
    NSDateComponents *dayComponents = [calendar components:(NSDayCalendarUnit) fromDate:date];
#endif
    
    return [dayComponents day];
}

+ (NSUInteger)month:(NSDate *)date {
    NSCalendar *calendar = [NSCalendar currentCalendar];
    
#if __IPHONE_OS_VERSION_MIN_REQUIRED >= __IPHONE_8_0
    // NSDayCalendarUnit
    NSDateComponents *dayComponents = [calendar components:(NSCalendarUnitMonth) fromDate:date];
#else
    NSDateComponents *dayComponents = [calendar components:(NSMonthCalendarUnit) fromDate:date];
#endif
    
    return [dayComponents month];
}

+ (NSUInteger)year:(NSDate *)date {
    NSCalendar *calendar = [NSCalendar currentCalendar];
    
#if __IPHONE_OS_VERSION_MIN_REQUIRED >= __IPHONE_8_0
    // NSDayCalendarUnit
    NSDateComponents *dayComponents = [calendar components:(NSCalendarUnitYear) fromDate:date];
#else
    NSDateComponents *dayComponents = [calendar components:(NSYearCalendarUnit) fromDate:date];
#endif
    
    return [dayComponents year];
}

+ (NSUInteger)hour:(NSDate *)date {
    NSCalendar *calendar = [NSCalendar currentCalendar];
    
#if __IPHONE_OS_VERSION_MIN_REQUIRED >= __IPHONE_8_0
    // NSDayCalendarUnit
    NSDateComponents *dayComponents = [calendar components:(NSCalendarUnitHour) fromDate:date];
#else
    NSDateComponents *dayComponents = [calendar components:(NSHourCalendarUnit) fromDate:date];
#endif
    
    return [dayComponents hour];
}

+ (NSUInteger)minute:(NSDate *)date {
    NSCalendar *calendar = [NSCalendar currentCalendar];
    
#if __IPHONE_OS_VERSION_MIN_REQUIRED >= __IPHONE_8_0
    // NSDayCalendarUnit
    NSDateComponents *dayComponents = [calendar components:(NSCalendarUnitMinute) fromDate:date];
#else
    NSDateComponents *dayComponents = [calendar components:(NSMinuteCalendarUnit) fromDate:date];
#endif
    
    return [dayComponents minute];
}

+ (NSUInteger)second:(NSDate *)date {
    NSCalendar *calendar = [NSCalendar currentCalendar];
    
#if __IPHONE_OS_VERSION_MIN_REQUIRED >= __IPHONE_8_0
    // NSDayCalendarUnit
    NSDateComponents *dayComponents = [calendar components:(NSCalendarUnitSecond) fromDate:date];
#else
    NSDateComponents *dayComponents = [calendar components:(NSSecondCalendarUnit) fromDate:date];
#endif
    
    return [dayComponents second];
}

+ (NSCalendar *)currentCalendar
{
    static NSCalendar *sharedCalendar = nil;
    if (!sharedCalendar)
        sharedCalendar = [NSCalendar autoupdatingCurrentCalendar];
    return sharedCalendar;
}
+ (NSDate *)dateWithDaysFromNow: (NSInteger) days
{
    return [[NSDate date] dateByAddingDays:days];
}
+ (NSDate *)dateYesterday
{
    return [NSDate dateWithDaysBeforeNow:1];
}
+ (NSDate *)dateWithDaysBeforeNow: (NSInteger) days
{
    return [[NSDate date] dateBySubtractingDays:days];
}
- (NSDate *)dateBySubtractingDays: (NSInteger) dDays
{
    return [self dateByAddingDays: (dDays * -1)];
}
- (NSDate *)dateByAddingDays: (NSInteger) dDays
{
    NSDateComponents *dateComponents = [[NSDateComponents alloc] init];
    [dateComponents setDay:dDays];
    NSDate *newDate = [[NSCalendar currentCalendar] dateByAddingComponents:dateComponents toDate:self options:0];
    return newDate;
}
- (BOOL)isEqualToDateIgnoringTime: (NSDate *) aDate
{
    NSDateComponents *components1 = [[NSDate currentCalendar] components:componentFlags fromDate:self];
    NSDateComponents *components2 = [[NSDate currentCalendar] components:componentFlags fromDate:aDate];
    return ((components1.year == components2.year) &&
            (components1.month == components2.month) &&
            (components1.day == components2.day));
}
- (BOOL)isToday
{
    return [self isEqualToDateIgnoringTime:[NSDate date]];
}
- (BOOL)isYesterday
{
    return [self isEqualToDateIgnoringTime:[NSDate dateYesterday]];
}
- (BOOL)isSameWeekAsDate: (NSDate *) aDate
{
    NSDateComponents *components1 = [[NSDate currentCalendar] components:componentFlags fromDate:self];
    NSDateComponents *components2 = [[NSDate currentCalendar] components:componentFlags fromDate:aDate];
    // Must be same week. 12/31 and 1/1 will both be week "1" if they are in the same week
    if (components1.weekOfYear != components2.weekOfYear) return NO;
    // Must have a time interval under 1 week. Thanks @aclark
    return (fabs([self timeIntervalSinceDate:aDate]) < D_WEEK);
}
- (BOOL)isThisWeek
{
    return [self isSameWeekAsDate:[NSDate date]];
}
- (BOOL)isSameYearAsDate: (NSDate *) aDate
{
    NSDateComponents *components1 = [[NSDate currentCalendar] components:NSCalendarUnitYear fromDate:self];
    NSDateComponents *components2 = [[NSDate currentCalendar] components:NSCalendarUnitYear fromDate:aDate];
    return (components1.year == components2.year);
}
- (BOOL)isThisYear{
    return [self isSameYearAsDate:[NSDate date]];
}
/**校验是否相差七天*/
- (BOOL)isContain7day{
    static NSDateFormatter *dateFormatter;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        dateFormatter = [[NSDateFormatter  alloc] init];
        [dateFormatter setDateFormat:@"yyyy-MM-dd"];
    });
    NSString *currentDay = [dateFormatter stringFromDate:[NSDate date]];//当前年月日
    NSString *theDay = [dateFormatter stringFromDate:self];//日期的年月日
    if([[dateFormatter dateFromString:currentDay] timeIntervalSinceDate:[dateFormatter dateFromString:theDay]] < 86400 * 7){
         return YES;
     }
    return NO;
}
- (nullable NSString *)weekDay{
    NSDateComponents *components = [[NSDate currentCalendar] components:componentFlags fromDate:self];
    if (components.weekday == 1) {
        return @"星期日 ";
    }else if (components.weekday == 2){
        return @"星期一 ";
    }else if (components.weekday == 3){
        return @"星期二 ";
    }else if (components.weekday == 4){
        return @"星期三 ";
    }else if (components.weekday == 5){
        return @"星期四 ";
    }else if (components.weekday == 6){
        return @"星期五 ";
    }else {
        return @"星期六 ";
    }
}
+ (NSString*)getIMDateTimeWithTimeSpace:(long long)sentTime{
    NSDate *timedate = [NSDate dateWithTimeIntervalSince1970:sentTime/1000];
    static NSDateFormatter *formatter ;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
       formatter = [[NSDateFormatter alloc] init];
    });
    NSString *confromTimespStr = nil;
    NSString *preString = @"";
    if (timedate.isToday) {  //当天
         [formatter setDateFormat:@"HH:mm"];
         return [formatter stringFromDate:timedate];
    }else if (timedate.isYesterday){ //昨天
         [formatter setDateFormat:@"HH:mm"];
         preString = @"昨天 ";
    }else if (timedate.isContain7day){ //本周
         [formatter setDateFormat:@"HH:mm"];
         preString = timedate.weekDay;
    }else{ //超过本周
         preString = @"";
         [formatter setDateFormat:@"yyyy年MM月dd日 HH:mm"];
    }
    confromTimespStr = [formatter stringFromDate:timedate];
    return [NSString stringWithFormat:@"%@%@",preString,confromTimespStr];
}
+ (NSString*)getDateTimeWithTimeSpace:(long long)sentTime{
    NSDate *timedate = [NSDate dateWithTimeIntervalSince1970:sentTime/1000];
    static NSDateFormatter *formatter ;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
       formatter = [[NSDateFormatter alloc] init];
    });
    NSString *confromTimespStr = nil;
    NSString *preString = @"";
    if (timedate.isToday) {  //当天
         [formatter setDateFormat:@"HH:mm"];
         return [formatter stringFromDate:timedate];
    }else if (timedate.isYesterday){ //昨天
         [formatter setDateFormat:@"HH:mm"];
         preString = @"昨天 ";
         return @"昨天";
    }else if (timedate.isContain7day){ //本周
         [formatter setDateFormat:@"HH:mm"];
         return timedate.weekDay;
    }else{ //超过本周
         preString = @"";
         [formatter setDateFormat:@"yyyy/MM/dd"];
    }
    confromTimespStr = [formatter stringFromDate:timedate];
    return [NSString stringWithFormat:@"%@%@",preString,confromTimespStr];
}

- (NSInteger)hoursBeforeDate: (NSDate *) aDate{
    NSTimeInterval ti = [aDate timeIntervalSinceDate:self];
    return (NSInteger) (ti / D_HOUR);
}
+ (long long)getBeforeDateTime:(long long)beforeTime nextTime:(long long)nextTime{
    long long  replyTime = fabs(nextTime - beforeTime);
    return replyTime;
}

//日期格式化
- (NSString *)stringWithFormat:(NSString *)format {
    NSDateFormatter *outputFormatter = [[NSDateFormatter alloc] init];
    [outputFormatter setDateFormat:format];
    NSString *timestamp_str = [outputFormatter stringFromDate:self];
    return timestamp_str;
}

//字符串转换成时间
+ (NSDate *)dateFromString:(NSString *)string withFormat:(NSString *)format
{
    NSDateFormatter *inputFormatter = [[NSDateFormatter alloc] init];
    [inputFormatter setDateFormat:format];
    NSDate *date = [inputFormatter dateFromString:string];
    return date;
}

//根据日期计算星座
+ (NSString *)getAstroWithMonth:(NSInteger)m day:(NSInteger)d
{
    
    NSString *astroString = @"摩羯水瓶双鱼白羊金牛双子巨蟹狮子处女天秤天蝎射手摩羯";
    NSString *astroFormat = @"102123444543";
    NSString *result;
    
    if (m<1||m>12||d<1||d>31){
        return @"错误日期格式!";
    }
    
    if(m==2 && d>29)
    {
        return @"错误日期格式!!";
    }
    else if(m==4 || m==6 || m==9 || m==11)
    {
        if (d>30)
        {
            return @"错误日期格式!!!";
        }
    }
    result=[NSString stringWithFormat:@"%@",[astroString substringWithRange:NSMakeRange(m*2-(d < [[astroFormat substringWithRange:NSMakeRange((m-1), 1)] intValue] - (-19))*2,2)]];
    return result;
}

///计算年龄
+ (NSInteger)ageWithDateOfBirth:(NSDate *)date;
{
    // 出生日期转换 年月日
    NSDateComponents *components1 = [[NSCalendar currentCalendar] components:NSDayCalendarUnit | NSMonthCalendarUnit | NSYearCalendarUnit fromDate:date];
    NSInteger brithDateYear  = [components1 year];
    NSInteger brithDateDay   = [components1 day];
    NSInteger brithDateMonth = [components1 month];
      
    // 获取系统当前 年月日
    NSDateComponents *components2 = [[NSCalendar currentCalendar] components:NSDayCalendarUnit | NSMonthCalendarUnit | NSYearCalendarUnit fromDate:[NSDate date]];
    NSInteger currentDateYear  = [components2 year];
    NSInteger currentDateDay   = [components2 day];
    NSInteger currentDateMonth = [components2 month];
      
    // 计算年龄
    NSInteger iAge = currentDateYear - brithDateYear - 1;
    if ((currentDateMonth > brithDateMonth) || (currentDateMonth == brithDateMonth && currentDateDay >= brithDateDay)) {
        iAge++;
    }
      
    return iAge;
}

+ (NSString *)dateFormatTimeInterval:(NSTimeInterval)timeInterval{
    NSDate *date = [NSDate dateWithTimeIntervalSince1970:timeInterval];
    NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
    [formatter setDateFormat:@"HH:mm:ss"];
    NSString *dateString = [formatter stringFromDate: date];
    return dateString;
}

+ (NSString *)getTimeInterval:(NSTimeInterval)timeInterval  formatter:(NSString *)formatter{
    NSDate *date = [NSDate dateWithTimeIntervalSince1970:timeInterval];
    NSDateFormatter * matter = [[NSDateFormatter alloc] init];
    [matter setDateFormat:formatter];
    NSString * timeString = [matter stringFromDate:date];
    return timeString;
}

#pragma mark 获取时间戳
+ (NSTimeInterval)getNowTimeInterval{
    NSDate* dat = [NSDate dateWithTimeIntervalSinceNow:0];
    NSTimeInterval a = [dat timeIntervalSince1970];
    return a;
}

@end
